﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Futaba.SBus
{
	/// <summary>
	/// A background service which retrieves bus-data from the supplied <see cref="Readers.ISbusStreamReader"/>
	/// and parses it
	/// </summary>
	public interface ISbusParsingService : INotifyPropertyChanged
	{
		/// <summary>
		/// Wether the service is currently running
		/// </summary>
		/// <seealso cref="Start"/>
		/// <seealso cref="Stop"/>
		bool IsRunning { get; }

		/// <summary>
		/// The <see cref="Telemetry.ITelemetryParser"/> to use. If not specified, 
		/// the <see cref="Telemetry.TelemetryParser.DefaultInstance"/> is used instead
		/// </summary>
		Telemetry.ITelemetryParser TelemetryParser { get; }

		/// <summary>
		/// The <see cref="Channels.IChannelParser"/> to use. If not specified, 
		/// the <see cref="Channels.ChannelParser.DefaultInstance"/> is used instead
		/// </summary>
		Channels.IChannelParser ChannelParser { get; }

		/// <summary>
		/// The reader which reads from the actual stream
		/// </summary>
		Readers.ISbusStreamReader Reader { get; }

		/// <summary>
		/// Wether <see cref="Channels.Channel"/> data was detected
		/// </summary>
		/// <remarks>
		/// If data is not retrieved via the transmitter, channel-data is usually not available
		/// (unless you are reading the stream from the receiver's S.BUS port)
		/// </remarks>
		bool ChannelDataAvailable { get; }
		
		/// <summary>
		/// Wether <see cref="Telemetry.Slot">Telemetry</see> data was detected
		/// </summary>
		bool TelemetryDataAvailable { get; }

		/// <summary>
		/// Raised when the <see cref="ISbusParsingService"/> is beginning to connect to the stream
		/// </summary>
		event EventHandler Starting;
		/// <summary>
		/// Raised when the <see cref="ISbusParsingService"/> has connected to the stream and
		/// the parser is processing data
		/// </summary>
		event EventHandler Started;
		/// <summary>
		/// Raised when the <see cref="ISbusParsingService"/> is beginning to disconnect from the stream
		/// </summary>
		event EventHandler Stopping;
		/// <summary>
		/// Raised when the <see cref="ISbusParsingService"/> has disconnected from the stream
		/// and the parser has ended processing data
		/// </summary>
		event EventHandler Stopped;

		/// <summary>
		/// Starts the background-service
		/// </summary>
		/// <param name="reader">The <see cref="Readers.ISbusStreamReader">reader</see> to use</param>
		/// <param name="parseChannels">if set, specifies wether to expect channel-data from the stream</param>
		/// <param name="parseTelemetry">if set, specifies wether to expect telemetry-data from the stream</param>
		/// <exception cref="InvalidOperationException">Raised, if only <paramref name="parseChannels"/> or <paramref name="parseTelemetry"/>
		/// is set, but not both</exception>
		/// <seealso cref="Starting"/>
		/// <seealso cref="Started"/>
		void Start(Readers.ISbusStreamReader reader, bool? parseChannels = null, bool? parseTelemetry = null);

		/// <summary>
		/// Stops the background-service
		/// </summary>
		/// <returns></returns>
		/// <seealso cref="Stopping"/>
		/// <seealso cref="Stopped"/>
		Task Stop();
	}
}
